package main

import "fmt"

func main() {
	// 创建一个切片并填充数据
	original := []int{1, 2, 3, 4, 5}
	fmt.Printf("Original初始状态: len=%d, cap=%d, 数据=%v\n", len(original), cap(original), original)

	// 通过切片引用original，切片共享同一内存
	shared := original
	fmt.Printf("Shared初始状态: len=%d, cap=%d, 数据=%v\n", len(shared), cap(shared), shared)

	// 打印原始切片和共享切片
	fmt.Println("Before modification:")
	fmt.Println("Original:", original)
	fmt.Println("Shared:", shared)

	// 修改原始切片的一个元素
	original[0] = 10
	// 因为shared和original共享底层数组，所以shared也会看到这个修改
	fmt.Println("\nAfter modifying original[0]=10:")
	fmt.Println("Original:", original)
	fmt.Println("Shared:", shared)

	// 修改共享切片的一个元素
	shared[1] = 20
	// 同样，original也会看到这个修改
	fmt.Println("\nAfter modifying shared[1]=20:")
	fmt.Println("Original:", original)
	fmt.Println("Shared:", shared)

	// 打印当前shared的容量
	fmt.Printf("\nBefore append - shared cap: %d\n", cap(shared))

	// 执行append操作，这可能会导致扩容
	// 当前shared的len=5, cap=5(因为是从original继承的)
	// 添加2个元素后len=7，超过cap=5，会触发扩容
	shared = append(shared, 1, 2)

	// 扩容后，shared会指向新的底层数组，与original不再共享
	fmt.Printf("After append - shared cap: %d\n", cap(shared))
	// 可以观察到容量通常会按一定策略增长(这里是10，即5 * 2)

	// 修改shared的新元素
	shared[2] = 30
	// 这个修改不会影响original，因为它们已经不再共享底层数组
	fmt.Println("\nAfter modifying shared[2]=30 (after append):")
	fmt.Println("Original:", original) // original不受影响
	fmt.Println("Shared:", shared)     // shared有新数据

	// 此时original和shared的关系:
	// 1. original仍然指向原来的底层数组
	// 2. shared指向新的更大的底层数组
	// 3. 两个切片的len和cap都不同了
	fmt.Println("\nFinal state:")
	fmt.Printf("Original: len=%d, cap=%d, 数据=%v\n", len(original), cap(original), original)
	fmt.Printf("Shared: len=%d, cap=%d, 数据=%v\n", len(shared), cap(shared), shared)
}
